package de.blitzcoder.collide.util;

import java.awt.event.ActionEvent;
import java.awt.event.KeyEvent;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.StringTokenizer;
import javax.swing.KeyStroke;

/**
 *
 * @author blitzcoder
 * This class creates and Parses KeyStrokes for Menus and Buttons
 */
public class KeyStrokeUtil {

    // Modifiers
    private static HashMap<String, Integer> keyModifiers;


    static {
        keyModifiers = new HashMap<String, Integer>();
        keyModifiers.put("ctrl", new Integer(ActionEvent.CTRL_MASK));
        keyModifiers.put("cmd", new Integer(ActionEvent.META_MASK)); // OSX
        keyModifiers.put("alt", new Integer(ActionEvent.ALT_MASK));
        keyModifiers.put("shift", new Integer(ActionEvent.SHIFT_MASK));
    }

    /*
     * This Method parses a Shortcut String like:
     * Strg+Alt+F4
     * Alt+C
     */
    public static KeyStroke parseKeyStroke(String xml) {

        xml = xml.replace(" ", "");
        StringTokenizer tokenizer = new StringTokenizer(xml, "+");

        int keyCode = 0;
        int modifier = 0;

        while (tokenizer.hasMoreTokens()) {
            String token = tokenizer.nextToken().toLowerCase();

            if (keyModifiers.containsKey(token)) {

                // A known modifier
                if (modifier == 0) {
                    modifier = keyModifiers.get(token).intValue();
                } else {
                    modifier = modifier | keyModifiers.get(token).intValue();
                }

            } else {

                // Check via relection
                try {
                    Class keyevent = KeyEvent.class;
                    Field f = keyevent.getDeclaredField("VK_" + token.toUpperCase());
                    keyCode = f.getInt(keyevent);
                } catch (Exception ex) {
                    // Key not available
                    throw new Error("Key " + token + " not known");
                }

            }

        }

        if (keyCode != 0) {

            return KeyStroke.getKeyStroke(keyCode, modifier);

        } else {
            return null;
        }

    }

    public static boolean isAltDown(KeyStroke s) {
        return (s.getModifiers() & ActionEvent.ALT_MASK) == ActionEvent.ALT_MASK;
    }

    public static boolean isCtrlDown(KeyStroke s) {
        return (s.getModifiers() & ActionEvent.CTRL_MASK) == ActionEvent.CTRL_MASK;
    }

    public static KeyStroke getKeyStroke(boolean ctrl,boolean alt,int keyCode) {
        int mod = 0;
        if (ctrl)
            mod = mod | ActionEvent.CTRL_MASK;
        if (alt)
            mod = mod | ActionEvent.ALT_MASK;
        return KeyStroke.getKeyStroke(keyCode,mod);
    }

}
